package com.rosense.nfvo.util;

import com.alibaba.fastjson2.JSON;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStreamWriter;
import java.net.URL;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.HashMap;
import java.util.Map;

import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import javax.net.ssl.TrustManager;
import javax.net.ssl.X509TrustManager;



/**
 * <p>
 * Description:[]
 * </p>
 *
 * @email peng.liu@rosense.net
 * @date 2021年1月15日 下午2:42:09
 */
public class HttpsUtils {

	public static void main(String[] args) {
//		Map<String,Object> paramMap = new HashMap<>();
//		paramMap.put("grantType", "password");
//		paramMap.put("userName", "NorthUser");
//		paramMap.put("value", "Changeme_123");
//		String url = "https://132.91.205.145:26335/api/rest/securityManagement/v1/oauth/token";
//		String result = sendHttpsMethod(url,JSON.toJSONString(paramMap),null,"POST",100);
//		System.out.println(result);
//		String token = new CsfmApiMain().getToken();
//		getHttpsDown(Config.getInstance().downUrl+"/nsmf/pm/v1/download/a4470cdd-cf45-4a17-92c1-1d451e2f6c47",
//				Config.getInstance().savePath,token);
		HwConfig config = HwConfig.getInstance();
		String tokenUrl = config.tokenUrl;
		Map<String, Object> paramMap = new HashMap<String, Object>();
		paramMap.put("username", config.username);
		paramMap.put("password", config.password);
		String result = HttpsUtils.sendHttpsMethod(tokenUrl, JSON.toJSONString(paramMap), null, "POST", config.tokenCode);//201
		System.out.println(result);
	}
	
	public static String sendHttpsMethod(String httpUrl,String json,String token,String method,Integer returnStatus){
		OutputStreamWriter out = null;
		InputStream is = null;
        String result = null;
		try {
			HttpsURLConnection.setDefaultHostnameVerifier(new HttpsUtils().new NullHostNameVerifier());
	        SSLContext sc = SSLContext.getInstance("TLS");
	        sc.init(null, trustAllCerts, new SecureRandom());
	        HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
			
			URL url = new URL(httpUrl);// 创建连接
			HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
			connection.setDoOutput(true);
			connection.setDoInput(true);
			connection.setUseCaches(false);
			connection.setInstanceFollowRedirects(true);
			connection.setRequestMethod(method) ; // 设置请求方式
			connection.setRequestProperty("Content-Type", "application/json"); // 设置发送数据的格式
			connection.setRequestProperty("Accept", "application/json;version=1.0"); // 设置接收数据的格式
//			connection.setRequestProperty("Accept-Language", "en-US");
			connection.setRequestProperty("X-Auth-Token",token);
			connection.connect();
			if("POST".equals(method)){
				out = new OutputStreamWriter(connection.getOutputStream(), "UTF-8"); // utf-8编码
				out.append(json);
				out.flush();
				out.close();
			}
            int status = connection.getResponseCode();
			if (status == returnStatus) {
				// 读取响应
				if(method.equals("DELETE")){
					result = httpUrl + " 删除完成";
				}else{
					is = connection.getInputStream();
					int length = (int) connection.getContentLength();// 获取长度
					if (length != -1) {
						byte[] data = new byte[length];
						byte[] temp = new byte[512];
						int readLen = 0;
						int destPos = 0;
						while ((readLen = is.read(temp)) > 0) {
							System.arraycopy(temp, 0, data, destPos, readLen);
							destPos += readLen;
						}
						result = new String(data, "UTF-8"); // utf-8编码
					}
				}
	            return result;
			} else {
//				is = connection.getErrorStream();
//				int length = (int) connection.getContentLength();// 获取长度
//				if (length != -1) {
//					byte[] data = new byte[length];
//					byte[] temp = new byte[512];
//					int readLen = 0;
//					int destPos = 0;
//					while ((readLen = is.read(temp)) > 0) {
//						System.arraycopy(temp, 0, data, destPos, readLen);
//						destPos += readLen;
//					}
//					result = new String(data, "UTF-8"); // utf-8编码
//				}
				result = connection.getResponseMessage();
				System.out.println("https请求token返回状态码:" + status + ",错误内容:" + result);
			}
			connection.disconnect();
		} catch (IOException e) {
            e.printStackTrace();
        } catch (NoSuchAlgorithmException e) {
			e.printStackTrace();
		} catch (KeyManagementException e) {
			e.printStackTrace();
		} finally {
            try {
            	if(is != null) {
                    is.close();
                }
            	if(out != null) {
                    out.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return "";
	}
	/**
	 * 下载https文件到本地
	 * @param httpUrl
	 * @param savePath
	 * @return
	 */
	public static String getHttpsDown(String httpUrl,String savePath,String token) {
		try {
			File path = new File(httpUrl);
			HttpsURLConnection.setDefaultHostnameVerifier(new HttpsUtils().new NullHostNameVerifier());
	        SSLContext sc = SSLContext.getInstance("TLS");
	        sc.init(null, trustAllCerts, new SecureRandom());
	        HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
	        
			URL url = new URL(httpUrl);// 创建连接
			HttpsURLConnection connection = (HttpsURLConnection) url.openConnection();
			connection.setDoOutput(true);
			connection.setDoInput(true);
			connection.setUseCaches(false);
			connection.setInstanceFollowRedirects(true);
			connection.setRequestMethod("GET") ; // 设置请求方式
			connection.setRequestProperty("Content-type", "application/octet-stream"); // 设置接收数据的格式
			connection.setRequestProperty("Connection", "Keep-Alive"); //维持长连接
//			connection.setRequestProperty("accessToken",token);
			connection.setRequestProperty("X-Auth-Token",token);
			connection.connect();
			
            int status = connection.getResponseCode();
			System.out.println("https下载返回状态码" + status);
			if (status == 200) {
				// 得到输入流
		        InputStream inputStream = connection.getInputStream();
		        // 获取自己数组
		        byte[] getData = readInputStream(inputStream);
		        
		        //文件保存位置
		        File saveDir = new File(savePath);
		        if(!saveDir.exists()){
		            saveDir.mkdirs();
		        }
		        File file = new File(saveDir+File.separator+path.getName());
		        FileOutputStream fos = new FileOutputStream(file);
		        fos.write(getData);
		        if(fos!=null){
		            fos.close();
		        }
		        if(inputStream!=null){
		            inputStream.close();
		        }
	            return "download success";
			}
			connection.disconnect();
		}  catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} catch (NoSuchAlgorithmException e) {
			e.printStackTrace();
		} catch (KeyManagementException e) {
			e.printStackTrace();
		} finally {
        }
        return "download fail";
	}
	
	/**
     * 从输入流中获取字节数组
     * @param inputStream
     * @return
     * @throws IOException
     */
    public static  byte[] readInputStream(InputStream inputStream) throws IOException {
        byte[] buffer = new byte[1024];
        int len = 0;
        ByteArrayOutputStream bos = new ByteArrayOutputStream();
        while((len = inputStream.read(buffer)) != -1) {
            bos.write(buffer, 0, len);
        }
        bos.close();
        return bos.toByteArray();
    }
	
	static TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager() {
		@Override
		public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
		}

		@Override
		public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
		}

		@Override
		public X509Certificate[] getAcceptedIssuers() {
			return null;
		}
	} };

	public class NullHostNameVerifier implements HostnameVerifier {
		@Override
		public boolean verify(String arg0, SSLSession arg1) {
			return true;
		}
	}
}
